---
title: Install Expo Router
description: Learn how to quickly get started by creating a new project with Expo Router or adding the library to an existing project.
sidebar_title: Installation
---

import { Terminal } from '~/ui/components/Snippet';
import { Step } from '~/ui/components/Step';
import { Tabs, Tab } from '~/ui/components/Tabs';

Find the steps below to create a new project with Expo Router library or add it to your existing project.

## Quick start

<Step label="1">

We recommend creating a new Expo app using `create-expo-app` to create a project with Expo Router library already installed and configured:

<Terminal cmd={['$ npx create-expo-app@latest']} />

</Step>

<Step label="2">

Now, you can start your project by running:

<Terminal cmd={['$ npx expo start']} />

- To view your app on a mobile device, we recommend starting with [Expo Go](/get-started/set-up-your-environment/#how-would-you-like-to-develop). As your application grows in complexity and you need more control, you can create a [development build](/develop/development-builds/introduction/).
- Open the project in a web browser by pressing <kbd>w</kbd> in the Terminal UI. Press <kbd>a</kbd> for Android (Android Studio is required), or <kbd>i</kbd> for iOS (macOS with Xcode is required).

</Step>

## Manual installation

Follow the steps below if you have a project that was previously created with Expo but does not have Expo Router library installed.

### Prerequisites

Make sure your computer is [set up for running an Expo app](/get-started/create-a-project/).

<Step label="1">

### Install dependencies

You'll need to install the following dependencies:

<Tabs>
  <Tab label="SDK 50 and above">
    <Terminal cmd={['$ npx expo install expo-router react-native-safe-area-context react-native-screens expo-linking expo-constants expo-status-bar']} />

    The above command will install versions of these libraries that are compatible with the Expo SDK version your project is using.

  </Tab>
  <Tab label="SDK 49 and below">
    <Terminal cmd={['$ npx expo install expo-router react-native-safe-area-context react-native-screens expo-linking expo-constants expo-status-bar react-native-gesture-handler']} />

    The above command will install versions of these libraries that are compatible with the Expo SDK version your project is using.

  </Tab>
</Tabs>

</Step>

<Step label="2">

### Setup entry point

For the property `main`, use the `expo-router/entry` as its value in the **package.json**. The initial client file is [**app/\_layout.js**](/router/advanced/root-layout).

```json package.json
{
  "main": "expo-router/entry"
}
```

</Step>

<Step label="3">

### Modify project configuration

Add a deep linking `scheme` in your [app config](/workflow/configuration/):

```json app.json
{
  "scheme": "your-app-scheme"
}
```

If you are developing your app for web, install the following dependencies:

<Terminal cmd={['$ npx expo install react-native-web react-dom']} />

Then, enable [Metro web](/guides/customizing-metro/#adding-web-support-to-metro) support by adding the following to your [app config](/workflow/configuration/):

```json app.json
{
  "web": {
    "bundler": "metro"
  }
}
```

</Step>

<Step label="4">

### Modify babel.config.js

<Tabs>

<Tab label="SDK 50 and above">

Ensure you use `babel-preset-expo` as the `preset`, in the **babel.config.js** file or delete the file:

```js babel.config.js
module.exports = function (api) {
  api.cache(true);
  return {
    presets: ['babel-preset-expo'],
  };
};
```

If you're upgrading from a version of Expo Router that is older than v3, remove the `plugins: ['expo-router/babel']`. `expo-router/babel` was merged in `babel-preset-expo` in SDK 50 (Expo Router v3).

</Tab>

<Tab label="SDK 49 and below">

Add `expo-router/babel` plugin as the last item in the `plugins` array to your project's **babel.config.js**:

{/* prettier-ignore */}
```js babel.config.js
module.exports = function (api) {
  api.cache(true);
  return {
    presets: ['babel-preset-expo'],
    /* @info Add the following line. */
    plugins: ['expo-router/babel'],
    /* @end */
  };
};
```

</Tab>

</Tabs>

</Step>

<Step label="5">

### Clear bundler cache

After updating the Babel config file, run the following command to clear the bundler cache:

<Terminal cmd={['$ npx expo start -c']} />

</Step>

<Step label="6">

### Update resolutions

<Tabs>

<Tab label="SDK 50 and above">
  If you're upgrading from an older version of Expo Router, ensure you remove all outdated Yarn
  resolutions or npm overrides in your **package.json**. Specifically, remove `metro`,
  `metro-resolver`, `react-refresh` resolutions from your **package.json**.
</Tab>

  <Tab label="SDK 49">
    Expo Router requires at least `react-refresh@0.14.0`. React Native hasn't upgraded as of SDK 49 and Expo Router v2, so you need to force upgrade your `react-refresh` version by setting a Yarn resolution or npm override.

    <Tabs>
      <Tab label="Yarn">
          ```json package.json
          {
            /* @hide ... */
            /* @end */
            "resolutions": {
              "react-refresh": "~0.14.0"
            }
          }
          ```
      </Tab>
      <Tab label="npm">
          ```json package.json
          {
            /* @hide ... */
            /* @end */
            "overrides": {
              "react-refresh": "~0.14.0"
            }
          }
          ```
      </Tab>
    </Tabs>

  </Tab>

</Tabs>
</Step>
